package device

import (
	"context"
	"gitee.com/wj008/hardware/libs"
	"sync"
	"sync/atomic"
)

type Manager struct {
	size int64
	data sync.Map
}

type IDevice interface {
	GetId() int
	GetNum() string
	GetKind() string
	GetWatch() []string
	KeepRun(context.Context)
	Stop()
	Setup(context.Context) error
	CatchData() error
	SingleRead(string, string) (any, error)
	SingleWrite(string, string, any) error
	MultiRead(libs.RMap) (map[string]any, error)
}

func (m *Manager) Get(key string) (dev IDevice, ok bool) {
	v, ok := m.data.Load(key)
	if ok {
		dev, ok = v.(IDevice)
	}
	return
}

// GetById 通过节点ID 获取节点
func (m *Manager) GetById(id int) (dev IDevice) {
	m.data.Range(func(k, v any) bool {
		nd := v.(IDevice)
		if nd.GetId() == id {
			dev = nd
			return false
		}
		return true
	})
	return dev
}
func (m *Manager) Has(key string) (ok bool) {
	_, ok = m.data.Load(key)
	return ok
}
func (m *Manager) Set(key string, dev IDevice) {
	ok := m.Has(key)
	m.data.Store(key, dev)
	if !ok {
		atomic.AddInt64(&m.size, 1)
	}
}
func (m *Manager) Delete(key string) {
	m.data.Delete(key)
	atomic.AddInt64(&m.size, -1)
}
func (m *Manager) Range(f func(key string, dev IDevice) bool) {
	m.data.Range(func(k, v any) bool {
		return f(k.(string), v.(IDevice))
	})
}
func (m *Manager) Clear() {
	m.data.Range(func(k, v any) bool {
		m.data.Delete(k)
		return true
	})
	atomic.StoreInt64(&m.size, 0)
}
func (m *Manager) Size() int64 {
	return atomic.LoadInt64(&m.size)
}
